package com.mac.web;

import com.alibaba.fastjson.JSON;
import com.mac.pojo.Messages;
import com.mac.pojo.User;
import com.mac.service.MessagesService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.servlet.ServletException;
import javax.servlet.annotation.WebServlet;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Date;

/**
 * 处理消息相关操作的Servlet。
 */
@WebServlet("/messagesServlet/*")
public class MessagesServlet extends BaseServlet {
    // 使用SLF4J记录日志
    private static final Logger LOGGER = LoggerFactory.getLogger("MessagesServlet.Class");
    // 注入消息服务类，用于与消息数据交互
    MessagesService messagesService = new MessagesService();

    /**
     * 插入消息的方法。
     * @param req 请求对象，包含请求信息。
     * @param resp 响应对象，用于返回响应数据。
     * @throws ServletException 如果发生Servlet异常。
     * @throws IOException 如果发生I/O异常。
     */
    public void insertMessages(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 设置请求的字符编码为UTF-8
        req.setCharacterEncoding("UTF-8");

        // 获取消息内容
        String content;
        try {
            content = req.getParameter("message");
            LOGGER.info("req.getParameter(\"message\") -> succeed");
        } catch (Exception e) {
            LOGGER.error("req.getParameter(\"message\") -> failed", e);
            throw new RuntimeException(e);
        }

        // 获取当前会话
        HttpSession session = req.getSession();

        // 获取用户ID
        Integer userId;
        try {
            User user = (User) session.getAttribute("user");
            if (user == null) {
                resp.getWriter().write("NotLogin");
                return;
            }
            userId = user.getUserId();
            LOGGER.info("(User) session.getAttribute(\"user\") -> succeed");
        } catch (NumberFormatException e) {
            LOGGER.error("(User) session.getAttribute(\"user\") -> failed", e);
            throw new RuntimeException(e);
        }

        // 验证消息内容是否为空
        if (content == null || content.trim().isEmpty()) {
            resp.getWriter().write("contentIsEmpty");
            return;
        }

        // 创建消息对象并设置属性
        Messages messages = new Messages();
        messages.setUserId(userId);
        messages.setContent(content);
        messagesService.insertMessage(messages);
        resp.getWriter().write("success");
    }

    /**
     * 根据ID查询单个消息的方法。
     * @param req 请求对象，包含请求信息。
     * @param resp 响应对象，用于返回响应数据。
     * @throws ServletException 如果发生Servlet异常。
     * @throws IOException 如果发生I/O异常。
     */
    public void selectMessagesById(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 从请求参数中获取消息ID
        int messageId = Integer.parseInt(req.getParameter("messageId"));
        Messages messages = null;
        if (!(messagesService.selectMessageById(messageId) == null)) {
            try {
                messages = messagesService.selectMessageById(messageId);
                LOGGER.info("selectMessageById -> succeed");
            } catch (Exception e) {
                LOGGER.error("selectMessageById -> failed", e);
                throw new RuntimeException(e);
            }
        } else {
            resp.getWriter().write("messageIdIsNotexist");
        }

        // 将消息对象转换为JSON格式
        String jsonString = JSON.toJSONString(messages);
        // 设置响应内容类型并写入JSON字符串
        resp.setContentType("text/json;charset=utf-8");
        resp.getWriter().write(jsonString);
    }

    /**
     * 根据用户ID查询用户的消息列表的方法。
     * @param req 请求对象，包含请求信息。
     * @param resp 响应对象，用于返回响应数据。
     * @throws ServletException 如果发生Servlet异常。
     * @throws IOException 如果发生I/O异常。
     */
    public void selectMessagesByUserId(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 从请求参数中获取用户ID
        int userId = Integer.parseInt(req.getParameter("userId"));
        ArrayList<Messages> messagesUserList = null;
        if (userId <= 0 || userId > 8) {
            resp.getWriter().write("userIdIsNotexist");
        } else {
            try {
                messagesUserList = messagesService.selectMessageByUserId(userId);
                LOGGER.info("messagesService.selectMessageByUserId() -> succeed");
            } catch (Exception e) {
                LOGGER.error("messagesService.selectMessageByUserId() -> failed", e);
                resp.getWriter().write("SAR_ERROR");
                return;
            }
        }
        // 将消息列表转换为JSON格式
        String jsonString = JSON.toJSONString(messagesUserList);
        // 设置响应内容类型并写入JSON字符串
        resp.setContentType("text/json;charset=utf-8");
        resp.getWriter().write(jsonString);
    }

    /**
     * 查询所有消息的方法。
     * @param req 请求对象，包含请求信息。
     * @param resp 响应对象，用于返回响应数据。
     * @throws ServletException 如果发生Servlet异常。
     * @throws IOException 如果发生I/O异常。
     */
    public void selectAllMessages(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        ArrayList<Messages> messagesList = new ArrayList<Messages>();
        try {
            messagesList = messagesService.selectAllMessages();
            LOGGER.info("messagesService.selectAllMessages() -> succeed");
        } catch (Exception e) {
            LOGGER.error("messagesService.selectAllMessages()) -> failed", e);
            resp.getWriter().write("SAR_ERROR");
            return;
        }
        // 将消息列表转换为JSON格式
        String jsonString = JSON.toJSONString(messagesList);
        // 设置响应内容类型并写入JSON字符串
        resp.setContentType("text/json;charset=utf-8");
        resp.getWriter().write(jsonString);
    }

    /**
     * 更新消息的方法。
     * @param req 请求对象，包含请求信息。
     * @param resp 响应对象，用于返回响应数据。
     * @throws ServletException 如果发生Servlet异常。
     * @throws IOException 如果发生I/O异常。
     */
    public void updateMessages(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 从请求参数中获取消息ID和用户ID
        int messageId = Integer.parseInt(req.getParameter("messageId"));
        int userId;
        try {
            userId = Integer.parseInt(req.getParameter("userId"));
            LOGGER.info("Integer.parseInt(req.getParameter(\"userId\")) -> succeed");
        } catch (NumberFormatException e) {
            LOGGER.error("Integer.parseInt(req.getParameter(\"userId\")) -> failed", e);
            throw new RuntimeException(e);
        }
        // 获取消息内容
        String content = null;
        try {
            content = req.getParameter("content");
            LOGGER.info("req.getParameter(\"message\") -> succeed");
        } catch (Exception e) {
            LOGGER.error("req.getParameter(\"message\") -> failed", e);
            throw new RuntimeException(e);
        }
        // 获取消息创建时间
        String createdAt;
        Date created;
        try {
            createdAt = req.getParameter("created_at");
            created = new Date(createdAt);
            LOGGER.info("req.getParameter(\"created_at\") -> succeed");
        } catch (Exception e) {
            LOGGER.error("req.getParameter(\"created_at\") -> failed", e);
            throw new RuntimeException(e);
        }
        // 验证用户ID是否存在
        if (userId <= 0 || userId > 8) {
            resp.getWriter().write("userIdIsNotexist");
            return;
        }
        // 验证消息内容是否为空
        if (content.trim().isEmpty()) {
            resp.getWriter().write("contentIsEmpty");
            return;
        }
        // 验证创建时间是否为空
        if (createdAt.trim().isEmpty()) {
            resp.getWriter().write("createdAtIsEmpty");
            return;
        }

        // 如果消息存在，则更新消息
        if (!(messagesService.selectMessageById(messageId) == null)) {
            Messages messages = new Messages();
            messages.setMessageId(messageId);
            messages.setUserId(userId);
            messages.setContent(content);
            messages.setCreatedAt((java.sql.Date) created);
            if (messagesService.updateMessage(messages)) {
                resp.getWriter().write("updateMessages successfully");
            }
            resp.getWriter().write("add messages successfully");
        }
    }

    /**
     * 删除消息的方法。
     * @param req 请求对象，包含请求信息。
     * @param resp 响应对象，用于返回响应数据。
     * @throws ServletException 如果发生Servlet异常。
     * @throws IOException 如果发生I/O异常。
     */
    public void deleteMessages(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
        // 从请求参数中获取消息ID
        int messageId = Integer.parseInt(req.getParameter("messageId"));
        // 如果消息不存在，则返回错误信息
        if (messagesService.selectMessageById(messageId) == null) {
            resp.getWriter().write("messageIdIsNotexist");
        } else {
            try {
                messagesService.deleteMessage(messageId);
                LOGGER.info("deleteMessages -> succeed");
            } catch (Exception e) {
                LOGGER.error("deleteMessages -> failed",e);
                throw new RuntimeException(e);
            }
            resp.getWriter().write("deleteMessages successfully");
        }
    }
}